﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using THenu.TinyHourseLib.DesignPattern.Behavioral_Patterns.Iterator_Pattern.RealWorld;

namespace THenu.TinyHourseLib.DesignPattern.Behavioral_Patterns.Iterator_Pattern
{
    class IteratorPattern : IPatternDemonstrate
    {
        public void StructuralCode()
        {
            ConcreteAggregate a = new ConcreteAggregate();
            a[0] = "Item A";
            a[1] = "Item B";
            a[2] = "Item C";
            a[3] = "Item D";

            // Create Iterator and provide aggregate
            ConcreteIterator i = new ConcreteIterator(a);

            Console.WriteLine("Iterating over collection:");

            object item = i.First();
            while (item != null)
            {
                Console.WriteLine(item);
                item = i.Next();
            }
        }

        public string PatternDescription()
        {
            string description = @"
Definition

Provide a way to access the elements of an aggregate object sequentially without exposing its underlying representation.

Participants

    The classes and objects participating in this pattern are:

Iterator  (AbstractIterator)
·defines an interface for accessing and traversing elements.
ConcreteIterator  (Iterator)
·implements the Iterator interface.
·keeps track of the current position in the traversal of the aggregate.
Aggregate  (AbstractCollection)
·defines an interface for creating an Iterator object
ConcreteAggregate  (Collection)
·implements the Iterator creation interface to return an instance of the proper ConcreteIterator";
            return description;
        }

        public void RealWorldExample()
        {
            // Build a collection
            THenu.TinyHourseLib.DesignPattern.Behavioral_Patterns.Iterator_Pattern.RealWorld.Collection collection = new RealWorld.Collection();
            collection[0] = new Item("Item 0");
            collection[1] = new Item("Item 1");
            collection[2] = new Item("Item 2");
            collection[3] = new Item("Item 3");
            collection[4] = new Item("Item 4");
            collection[5] = new Item("Item 5");
            collection[6] = new Item("Item 6");
            collection[7] = new Item("Item 7");
            collection[8] = new Item("Item 8");

            // Create iterator
            RealWorld.Iterator iterator = new RealWorld.Iterator(collection);

            // Skip every other item
            iterator.Step = 2;

            Console.WriteLine("Iterating over collection:");

            for (Item item = iterator.First();
                !iterator.IsDone; item = iterator.Next())
            {
                Console.WriteLine(item.Name);
            }
        }
    }
}
